<?php

declare(strict_types=1);

use think\facade\Db;
use think\migration\Migrator;

class SeedReferenceData extends Migrator
{
    public function up(): void
    {
        $basePath = dirname(__DIR__);

        $this->seedCategories($basePath . '/best_category.csv');
        $this->seedBrands($basePath . '/best_brand.csv');
        $this->seedRegions($basePath . '/bearing_reg.csv');
    }

    public function down(): void
    {
        Db::name('prod_category')->delete(true);
        Db::name('prod_brand')->delete(true);
        Db::name('region')->delete(true);
    }

    private function seedCategories(string $file): void
    {
        if (!is_file($file)) {
            return;
        }

        Db::name('prod_category')->delete(true);

        $handle = fopen($file, 'r');
        if ($handle === false) {
            return;
        }

        $header = fgetcsv($handle);
        if (!$header) {
            fclose($handle);
            return;
        }

        while (($row = fgetcsv($handle)) !== false) {
            $data = array_combine($header, $row);
            if (!$data) {
                continue;
            }

            Db::name('prod_category')->insert([
                'id' => (int) ($data['id'] ?? 0),
                'name' => $this->str($data['name'] ?? ''),
                'slug' => $this->str($data['slug'] ?? $data['name'] ?? ''),
                'parent_id' => (int) ($data['parent_id'] ?? 0),
                'level' => (int) ($data['level'] ?? 1),
                'path' => $this->str($data['path'] ?? ''),
                'icon_url' => $this->str($data['icon_url'] ?? ''),
                'cover_url' => $this->str($data['cover_url'] ?? ''),
                'description' => $this->str($data['description'] ?? ''),
                'content' => $this->nullable($data['content'] ?? null),
                'sort' => (int) ($data['sort'] ?? 0),
                'is_visible' => (int) ($data['is_visible'] ?? 1),
                'create_time' => $this->now(),
                'update_time' => $this->now(),
            ]);
        }

        fclose($handle);
    }

    private function seedBrands(string $file): void
    {
        if (!is_file($file)) {
            return;
        }

        Db::name('prod_brand')->delete(true);

        $handle = fopen($file, 'r');
        if ($handle === false) {
            return;
        }

        $header = fgetcsv($handle);
        if (!$header) {
            fclose($handle);
            return;
        }

        while (($row = fgetcsv($handle)) !== false) {
            $data = array_combine($header, $row);
            if (!$data) {
                continue;
            }

            Db::name('prod_brand')->insert([
                'id' => (int) ($data['id'] ?? 0),
                'name' => $this->str($data['name'] ?? ''),
                'slug' => $this->str($data['slug'] ?? $data['name'] ?? ''),
                'logo_url' => $this->str($data['logo'] ?? ''),
                'banner_url' => $this->str($data['banner_url'] ?? ''),
                'description' => $this->str($data['description'] ?? ''),
                'content' => $this->nullable($data['content'] ?? null),
                'origin_country' => $this->str($data['origin_country'] ?? ''),
                'owner_org_id' => null,
                'sort' => (int) ($data['sort'] ?? 0),
                'is_visible' => (int) ($data['is_visible'] ?? 1),
                'create_time' => $this->now(),
                'update_time' => $this->now(),
            ]);
        }

        fclose($handle);
    }

    private function seedRegions(string $file): void
    {
        if (!is_file($file)) {
            return;
        }

        Db::name('region')->delete(true);

        $handle = fopen($file, 'r');
        if ($handle === false) {
            return;
        }

        $header = fgetcsv($handle);
        if (!$header) {
            fclose($handle);
            return;
        }

        while (($row = fgetcsv($handle)) !== false) {
            $data = array_combine($header, $row);
            if (!$data) {
                continue;
            }

            Db::name('region')->insert([
                'id' => (int) ($data['id'] ?? 0),
                'name' => $this->str($data['name'] ?? ''),
                'code' => $this->str($data['code'] ?? $data['name'] ?? ''),
                'parent_id' => (int) ($data['parent_id'] ?? 0),
                'level' => (int) ($data['level'] ?? 1),
                'path' => $this->str($data['path'] ?? ''),
                'sort' => (int) ($data['sort'] ?? 0),
                'status' => (int) ($data['status'] ?? 1),
                'seller_customer_count' => 0,
                'buyer_customer_count' => 0,
                'create_time' => $this->now(),
                'update_time' => $this->now(),
            ]);
        }

        fclose($handle);
    }

    private function str($value, string $default = ''): string
    {
        if ($value === null) {
            return $default;
        }
        $trimmed = trim((string) $value);
        if ($trimmed === '' || strtoupper($trimmed) === 'NULL') {
            return $default;
        }
        return $trimmed;
    }

    private function nullable($value): ?string
    {
        if ($value === null) {
            return null;
        }
        $trimmed = trim((string) $value);
        if ($trimmed === '' || strtoupper($trimmed) === 'NULL') {
            return null;
        }
        return $trimmed;
    }

    private function now(): string
    {
        return date('Y-m-d H:i:s');
    }
}
